package com.gjh.xiaokabang2code.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.gjh.xiaokabang2code.async.SendMailToNewUser;
import com.gjh.xiaokabang2code.common.BusinessException;
import com.gjh.xiaokabang2code.common.DesUtil;
import com.gjh.xiaokabang2code.common.ErrorCode;
import com.gjh.xiaokabang2code.common.HideCharactersUtil;
import com.gjh.xiaokabang2code.mapper.BankcardMapper;
import com.gjh.xiaokabang2code.mapper.UserInfoMapper;
import com.gjh.xiaokabang2code.mapper.UserMapper;
import com.gjh.xiaokabang2code.model.Bankcard;
import com.gjh.xiaokabang2code.model.User;
import com.gjh.xiaokabang2code.model.UserInfo;
import com.gjh.xiaokabang2code.model.request.UpdateUserRt;
import com.gjh.xiaokabang2code.model.response.LoginRs;
import com.gjh.xiaokabang2code.model.response.SafetyUserRs;
import com.gjh.xiaokabang2code.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.util.Date;
import java.util.List;
import java.util.UUID;
import java.util.regex.Pattern;

import static com.gjh.xiaokabang2code.constant.UserConstant.USER_LOGIN_KEY;


/**
 * @author tsin0
 * @description 针对表【user】的数据库操作Service实现
 * @createDate 2024-03-07 17:38:00
 */
@Service
@Transactional(rollbackFor = Exception.class)
public class UserServiceImpl extends ServiceImpl<UserMapper, User>
        implements UserService {

    @Resource
    private UserMapper userMapper;

    @Resource
    private UserInfoMapper userInfoMapper;

    @Resource
    private BankcardMapper bankcardMapper;

    public static final String SALT = "XiaoKabang2Bygjh2003";

    @Autowired
    private SendMailToNewUser sendMailToNewUser;

    @Override
    public String login(String uId, HttpServletRequest httpServletRequest) throws Exception {
        //纯数字
        boolean matches = Pattern.matches("\\d+", uId);
        if (!matches) {
            throw new BusinessException(ErrorCode.PARAMS_ERROR, "学号包含除数字外符号（S1001）");
        }
        //10位
        if (uId.length() != 10) {
            throw new BusinessException(ErrorCode.PARAMS_ERROR, "学号长度不是10位（S1002）");
        }
        //先查询注册情况
        QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
        userQueryWrapper.eq("u_id", uId);
        List<User> users = userMapper.selectList(userQueryWrapper);
        if (users.size() > 1) {
            throw new BusinessException(ErrorCode.SYSTEM_ERROR, "数据数目大于1,可能是数据有污染？（S1003）");
        }
        if (!users.isEmpty()) {
            //记录登录状态
            LoginRs loginRs = new LoginRs();
            loginRs.setUc(users.get(0).getUc());
            loginRs.setUId(users.get(0).getUId());
            httpServletRequest.getSession().setAttribute(USER_LOGIN_KEY, loginRs);
            return loginRs.getUc();
        }
        //新用户
        //查userInfor库,如果有直接是用
        QueryWrapper<UserInfo> userInfoQueryWrapper = new QueryWrapper<>();
        userInfoQueryWrapper.eq("u_id", uId);
        List<UserInfo> userInfos = userInfoMapper.selectList(userInfoQueryWrapper);
        if (userInfos.size() > 1) {
            throw new BusinessException(ErrorCode.SYSTEM_ERROR, "数据数目大于1,可能是源数据有污染？（S1003）");
        }

        if (userInfos.isEmpty()) {
            User user = new User();
            user.setUc(String.valueOf(UUID.randomUUID()));
            user.setUId(uId);
            user.setCreateTime(new Date());
            boolean save = this.save(user);
            if (!save) {
                throw new BusinessException(ErrorCode.PARAMS_ERROR, "新增用户失败(S1004)");
            }
            Bankcard bankcard = new Bankcard();
            bankcard.setUId(uId);
            bankcard.setUBankcard("");
            bankcard.setCreateTime(new Date());
            int insert = bankcardMapper.insert(bankcard);
            if (insert <= 0) {
                throw new BusinessException(ErrorCode.PARAMS_ERROR, "新增用户银行卡失败(S1004)");
            }
            //记录登录状态
            LoginRs loginRs = new LoginRs();
            loginRs.setUc(user.getUc());
            loginRs.setUId(user.getUId());
            httpServletRequest.getSession().setAttribute(USER_LOGIN_KEY, loginRs);
            sendMailToNewUser.preSendMailToNewUser(uId);
            return loginRs.getUc();
        }
        UserInfo userInfo = userInfos.get(0);
        User user = new User();
        user.setUc(String.valueOf(UUID.randomUUID()));
        user.setUId(uId);
        user.setUName(userInfo.getUName());
        user.setUClass(userInfo.getUClass());
        user.setUDepartment(userInfo.getUDepartment());
        user.setCreateTime(new Date());
        boolean save = this.save(user);
        if (!save) {
            throw new BusinessException(ErrorCode.PARAMS_ERROR, "新增用户失败(S1005)");
        }
        Bankcard bankcard = new Bankcard();
        bankcard.setUId(uId);
        bankcard.setUBankcard("");
        bankcard.setCreateTime(new Date());
        int insert = bankcardMapper.insert(bankcard);
        if (insert <= 0) {
            throw new BusinessException(ErrorCode.PARAMS_ERROR, "新增用户银行卡失败(S1004)");
        }
        //记录登录状态
        LoginRs loginRs = new LoginRs();
        loginRs.setUc(user.getUc());
        loginRs.setUId(user.getUId());
        httpServletRequest.getSession().setAttribute(USER_LOGIN_KEY, loginRs);
        sendMailToNewUser.preSendMailToNewUser(uId);
        return loginRs.getUc();
    }

    @Override
    public SafetyUserRs getSafetyUser(LoginRs loginUser) throws Exception {
        String uId = loginUser.getUId();
        QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
        userQueryWrapper.eq("u_id", uId);
        List<User> users = userMapper.selectList(userQueryWrapper);
        if (users.isEmpty()) {
            throw new BusinessException(ErrorCode.REPEATING_DATA, "数据库没有该条数据(S2001)");
        }
        if (users.size() > 1) {
            throw new BusinessException(ErrorCode.REPEATING_DATA, "数据数目大于1?(S2002)");
        }
        //库里有
        User user = users.get(0);
        QueryWrapper<Bankcard> bankcardQueryWrapper = new QueryWrapper<>();
        bankcardQueryWrapper.eq("u_id",user.getUId());
        List<Bankcard> bankcards = bankcardMapper.selectList(bankcardQueryWrapper);
        if (bankcards.isEmpty()) {
            throw new BusinessException(ErrorCode.REPEATING_DATA, "数据库没有该条数据(S2003)");
        }
        if (bankcards.size() > 1) {
            throw new BusinessException(ErrorCode.REPEATING_DATA, "数据数目大于1?(S2004)");
        }
        Bankcard bankcard = bankcards.get(0);
        SafetyUserRs safetyUserRs = new SafetyUserRs();
        safetyUserRs.setUc(user.getUc());
        safetyUserRs.setUId(user.getUId());
        safetyUserRs.setUName(HideCharactersUtil.reservedFirstWord(user.getUName()));
        safetyUserRs.setUClass(user.getUClass());
        safetyUserRs.setNamePrivacy(user.getNamePrivacy());
        safetyUserRs.setUDepartment(user.getUDepartment());
        safetyUserRs.setUPhone(HideCharactersUtil.phoneHideDigits(new DesUtil(SALT).decrypt(user.getUPhone(), "CBC"),3,7));
        safetyUserRs.setUBankcard(HideCharactersUtil.convertToFourDigits(new DesUtil(SALT).decrypt(bankcard.getUBankcard(), "CBC")));
        safetyUserRs.setBankcardStatus(bankcard.getBankcardStatus());
        return safetyUserRs;
    }

    @Override
    public Boolean updateUser(UpdateUserRt updateUserRt, LoginRs loginUser) throws Exception {
        QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
        userQueryWrapper.eq("u_id", loginUser.getUId());
        User user = new User();
        if(!updateUserRt.getUPhone().isEmpty()){
            user.setUPhone(new DesUtil(SALT).encrypt(updateUserRt.getUPhone(), "CBC"));
        }
        if(!updateUserRt.getUName().isEmpty()){
            user.setUName(updateUserRt.getUName());
        }
        if(!updateUserRt.getUClass().isEmpty()){
            user.setUClass(updateUserRt.getUClass());
        }
        if(!updateUserRt.getUDepartment().isEmpty()){
            user.setUDepartment(updateUserRt.getUDepartment());
        }
        if(updateUserRt.getNamePrivacy()!=null&&(updateUserRt.getNamePrivacy()==0||updateUserRt.getNamePrivacy()==1)){
            user.setNamePrivacy(updateUserRt.getNamePrivacy());
        }
        user.setUpdateTime(new Date());

        if(!updateUserRt.getUBankcard().isEmpty()){
            QueryWrapper<Bankcard> bankcardQueryWrapper = new QueryWrapper<>();
            bankcardQueryWrapper.eq("u_id", loginUser.getUId());
            Bankcard bankcard = new Bankcard();
            bankcard.setUBankcard(new DesUtil(SALT).encrypt(updateUserRt.getUBankcard(), "CBC"));
            int update = bankcardMapper.update(bankcard, bankcardQueryWrapper);
            if(update<=0){
                throw new BusinessException(ErrorCode.PARAMS_ERROR, "新增失败(S2002)");
            }
        }
        int result = userMapper.update(user,userQueryWrapper);
        if(result<0) {
            throw new BusinessException(ErrorCode.PARAMS_ERROR, "新增失败(S2002)");
        }
        return true;
    }

}

